#include "d3dUtility.h"
#include "rvASSEMBLECUBE.h"

IDirect3DDevice9*    g_pDevice        = NULL;
IDirectInputDevice8* g_pDIDevKeyboard = NULL;
IDirectInputDevice8* g_pDIDevMouse    = NULL;

rvASSEMBLECUBE* g_pAssembleCube = NULL;

bool g_bWireframe = false;

bool Setup()
{
	g_pAssembleCube = new rvASSEMBLECUBE(g_pDevice, g_pDIDevKeyboard, g_pDIDevMouse);

	g_pDevice->SetSamplerState(0, D3DSAMP_MAGFILTER, D3DTEXF_LINEAR);
	g_pDevice->SetSamplerState(0, D3DSAMP_MINFILTER, D3DTEXF_LINEAR);
	g_pDevice->SetSamplerState(0, D3DSAMP_MIPFILTER, D3DTEXF_LINEAR);

	g_pDevice->SetRenderState(D3DRS_NORMALIZENORMALS, true);
	g_pDevice->SetRenderState(D3DRS_SPECULARENABLE, true);

	D3DXMATRIX proj;
	D3DXMatrixPerspectiveFovLH(&proj, D3DX_PI * 0.5f/*90 - degree*/, (float)d3d::WIDTH / (float)d3d::HEIGHT, 1.0f, 1000.0f);
	g_pDevice->SetTransform(D3DTS_PROJECTION, &proj);

//	g_pDevice->SetRenderState( D3DRS_MULTISAMPLEANTIALIAS, true );

	return true;
}

void Cleanup()
{
	if( g_pAssembleCube )
		d3d::Delete<rvASSEMBLECUBE*>(g_pAssembleCube);
}

bool Display(float timeDelta)
{
	if( g_pDevice )
	{			
		g_pDevice->SetRenderState( D3DRS_FILLMODE, g_bWireframe ? D3DFILL_WIREFRAME : D3DFILL_SOLID );

		g_pDevice->Clear(0, 0, D3DCLEAR_TARGET | D3DCLEAR_ZBUFFER, 0xff000000, 1.0f, 0);
		g_pDevice->BeginScene();

		g_pAssembleCube->draw(timeDelta);

		g_pDevice->EndScene();
		g_pDevice->Present(0, 0, 0, 0);
	}
	return true;
}

LRESULT CALLBACK d3d::WndProc(HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
	switch( msg )
	{
	case WM_DESTROY:
		::PostQuitMessage(0);
		break;

	case WM_ENTERMENULOOP:
		if( g_pDIDevMouse )
			g_pDIDevMouse->Unacquire();
		break;

	case WM_EXITMENULOOP:
		if( g_pDIDevMouse )
			g_pDIDevMouse->Acquire();
		break;
            
	case WM_ACTIVATE:
		if( WA_INACTIVE != wParam && g_pDIDevKeyboard )
			g_pDIDevKeyboard->Acquire();
		if( WA_INACTIVE != wParam && g_pDIDevMouse )
			g_pDIDevMouse->Acquire();
		break;

	case WM_KEYDOWN:
		switch( wParam )
		{
		case '9':
			g_bWireframe = !g_bWireframe;
			break;
		}
		break;
	}
	return ::DefWindowProc(hWnd, msg, wParam, lParam);
}

int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE prevInstance, PSTR cmdLine, int showCmd)
{
	HWND hWnd = NULL;

	if( !d3d::InitD3D(hWnd, hInstance, D3DDEVTYPE_HAL, &g_pDevice) )
	{
		::MessageBox(0, "InitD3D() - FAILED", 0, 0);
		return 0;
	}

	if( !d3d::InitD3DInput(hWnd, &g_pDIDevKeyboard, &g_pDIDevMouse) )
	{
		::MessageBox(0, "InitD3DInput() - FAILED", 0, 0);
		return 0;
	}

	if( !Setup() )
	{
		::MessageBox(0, "Setup() - FAILED", 0, 0);
		return 0;
	}

	d3d::EnterMsgLoop( Display );

	Cleanup();

	g_pDIDevKeyboard->Release();
	g_pDIDevMouse->Release();

	g_pDevice->Release();

	return 0;
}